#!/bin/bash

# Copyright (C) 2010, 2011, 2012, 2013 Embecosm Limited
# Copyright (C) 2013-2017 Synopsys, Inc.

# Contributor Jeremy Bennett <jeremy.bennett@embecosm.com>
# Contributor Joern Rennecke <joern.rennecke@embecosm.com>
# Contributor Anton Kolesov <Anton.Kolesov@synopsys.com>

# This file is additional DejaGnu procs to support telnet based testing.

# This program is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by the Free
# Software Foundation; either version 3 of the License, or (at your option)
# any later version.

# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
# more details.

# You should have received a copy of the GNU General Public License along
# with this program.  If not, see <http://www.gnu.org/licenses/>.

#		ARC Bare Metal DejaGnu nSim Simulator Support
#		=============================================

# This board specification is for use with the ARC nSim simulator.

# TODO: This board has some shared code with arc-sim-nsim.exp - it should be
# extracted into separate file.

# This is a list of toolchains that are supported on this board.
set_board_info target_install ${target_triplet}

# Load the generic configuration for this board. This will define a basic set
# of routines needed by the tool to communicate with the board. Depends on the
# tool.
load_generic_config "gdb-comm"

# Some extra procs for testing with nSim. This must go after gdb-comm, as it
# overrides one of the function in gdb-comm.
search_and_load_file "library file" "nsim-extra.exp" ${boards_dir}

# Load procedures for enabling support of compatibility tests (compat.exp
# from GCC testsuite).
search_and_load_file "library file" "tool-extra.exp" ${boards_dir}
search_and_load_file "library file" "arc-common.exp" ${boards_dir}

# GDB tests require special treatment, they ignore "gdb-comm" configuration
# unless "monitor" GDB test suite configuration is loaded.
if { $tool == "gdb" } {
	load_lib "../config/monitor.exp"
}

# Use nSIM GNU IO hostlink
set_board_info arc,hostlink "nsim"

# Any multilib options are set in an environment variable.
process_multilib_options [arc_get_multilib_options]

set xldflags "-Wl,--defsym=__DEFAULT_HEAP_SIZE=256m -Wl,--defsym=__DEFAULT_STACK_SIZE=1024m"

# We only support newlib on this target. We assume that all multilib
# options have been specified before we get here.
set_board_info compiler  "[find_gcc]"
set_board_info cflags    "[libgloss_include_flags] [newlib_include_flags] [arc_get_cflags]"
set_board_info ldflags   "[libgloss_link_flags] ${xldflags} [newlib_link_flags]"

# No linker script needed.
set_board_info ldscript ""

set_board_info nsim_exe $env(NSIM_HOME)/bin/nsimdrv

set nsim_flags {}
# Run nSIM as gdbserver
lappend nsim_flags -gdb
# Do not exit after client disconnects
lappend nsim_flags -reconnect

# Detect if nSIM Turbo is available and libstdc++ is being tested.  Most of the
# Dejagnu tests do not benefit from Turbo mode, because they are extremely
# small, hence they finish before Turbo can kick in.  However there is two
# certain floating point tests in libstdc++ that take quite a lot of time to
# execute with soft-FP - around 15 minutes on Xeon@3.5GHz host.  Enabling Turbo
# reduces this time to mere 1 minute.
if { $tool == "libstdc++" } {
    spawn [board_info $::board nsim_exe] -on nsim_fast
    expect {
	"Download failed: no file name specified" {
	    verbose "nSIM Turbo is available"
	    lappend nsim_flags "-on nsim_fast"
	}
	default {
	    # nSIM would spit out an error message if Turbo is not supported.
	    verbose "nSIM Turbo is not available, increasing timeout"
	    set_board_info sim_time_limit 1200
	}
    }
}

# Check if nsim_download_elf_sections option is required - whether nSIM version
# is > 2015.06. If revision.txt doesn't exist - this is a private verification
# build of nSIM, so assume that this is the latest version.
set nsim_version_path "$::env(NSIM_HOME)/revision.txt"
if [file exists $nsim_version_path] {
    set nsim_version_fid [open $nsim_version_path r]
    set nsim_version_text [read $nsim_version_fid]
    close $nsim_version_fid
    regexp "Version\\s+: (\\d+)\.(\\d+)" $nsim_version_text -> \
	nsim_version_year nsim_version_month
    if { $nsim_version_year > 2015 || \
	($nsim_version_year == 2015 && $nsim_version_month > 6) } {
	# Avoid performance penalty of useless initialization of heap and stack
	# sections.
	lappend nsim_flags "-on nsim_download_elf_sections"
    }
} else {
    lappend nsim_flags "-on nsim_download_elf_sections"
}

set_board_info nsim_flags [join $nsim_flags]

# nSIM is an exclusive resource -- only one client can connect at a time.
# Using script that generates random port allows to leave management of nSIM
# instances to dejagnu -- it will start, reboot and kill them as needed.
# get-random-port.sh verifies that generated is free, there is still
# probability of collision due to race conditions, but it is much less than in
# other situations.  Call to nsim_open will set the netport (used by gdb-comm)
# as well as setting up nSim specific data.
set port [exec [file dirname $env(DEJAGNU)]/get-random-port.sh]
nsim_open $port

# GDB protocol to be used
set_board_info gdb_protocol "remote"

# Use 'continue' instead of 'run' when executing a test
set_board_info gdb_run_command "continue"

# On occations GDB cannot connect to nSIM and reboots it. By default amount of
# reboots is limited to 15, after that all execution tests will be reported as
# UNTESTED. We need to set an effectively infinite number of reboots so that
# all execute tests will finish.
set_board_info max_reload_reboots 1500000

# Doesn't pass arguments or signals, can't return results, and doesn't
# do inferiorio.
set_board_info noargs 1
set_board_info gdb,nosignals 1
set_board_info gdb,noresults 1
set_board_info gdb,noinferiorio 1
set_board_info needs_status_wrapper ""

if { $tool == "gdb" } {
	# We use gdbserver to run applications
	set_board_info use_gdb_stub 1
	# GDB jumps to start_symbols after loading. Default value is `start'.
	set_board_info gdb,start_symbol "__start"
	set_board_info gdb,do_reload_on_run 1
	set_board_info gdb,no_hardware_watchpoints 1
	# This duplicates the one without 'gdb,'
	set_board_info gdb,noargs 1
	set_board_info gdb,nofileio 1
}

# Tests may recognize this board as a simulator and reduce amount
# of computations.
set_board_info is_simulator 1

# Turn on support of compat.exp tests from GCC testsuite if environment
# variable ARC_GCC_COMPAT_SUITE == 1.
if { [info exists env(ARC_GCC_COMPAT_SUITE)] } {
    set is_gcc_compat_suite $env(ARC_GCC_COMPAT_SUITE)
} else {
    if { ![info exists is_gcc_compat_suite] } {
	set is_gcc_compat_suite 0
    }
}

if { $is_gcc_compat_suite } {
    fix_gcc_compat_multilib_flags
}

# vim: noexpandtab sts=4 ts=8:
